const express = require("express");
const apiRouter = express.Router();
const { Client } = require("ssh2");
const multer = require("multer");
const fs = require("fs");
const { saveFileData } = require("../../models/middleware");
const WebSocket = require("ws");
const { Terminal } = require("xterm-headless");
const app = express();

const config = global.config.server;

// 存储所有的 WebSocket 连接
const wss = new WebSocket.Server({ noServer: true });

// 存储每个连接对应的终端实例
const terminals = new Map();

const upload = multer({ dest: "uploads/" }); //文件上传的位置

//  引入 SSH 连接和执行命令的公共方法
const executeSSHCommand = require("../../models/executeSSHCommand");

apiRouter.post("/getServeFiles", async (req, res) => {
  try {
    let parmse = req.body;
    const filePath = parmse.filePath;
    // 添加 -F 选项来显示文件类型指示符
    const command = `ls -lF ${filePath}`;

    executeSSHCommand(command, (err, output) => {
      if (err) {
        return res.send({
          code: 50000,
          msg: err.message,
        });
      }

      // 处理输出，将其转换为数组
      const lines = output.split("\n");

      const fileInfoArray = [];
      const directory = filePath;

      // 跳过第一行，因为它通常是总计信息
      for (let i = 1; i < lines.length; i++) {
        const line = lines[i].trim();
        if (line) {
          const parts = line.split(/\s+/);
          if (parts.length >= 9) {
            let filePath = "";
            if (directory === "/") {
              filePath = `/${parts.slice(8).join("")}`;
            } else {
              filePath = `${directory}/${parts.slice(8).join("")}`;
            }
            if (filePath[filePath.length - 1] == "/") {
              // 删除最后一个元素的斜杠
              filePath = filePath.slice(0, -1);
            }

            // 处理月份缩写为数字
            const monthMap = {
              Jan: "01",
              Feb: "02",
              Mar: "03",
              Apr: "04",
              May: "05",
              Jun: "06",
              Jul: "07",
              Aug: "08",
              Sep: "09",
              Oct: "10",
              Nov: "11",
              Dec: "12",
            };
            const monthNumber = monthMap[parts[5]];
            const day = parts[6].padStart(2, "0");
            let year;
            if (parts[7].includes(":")) {
              // 如果是时间格式，则使用当前年份
              const currentDate = new Date();
              year = currentDate.getFullYear();
            } else {
              year = parts[7];
            }
            const formattedDate = `${year}-${monthNumber}-${day}`;

            // 提取文件名和文件类型指示符
            const fullName = parts.slice(8).join("");
            let name = fullName;
            let fileType = "";
            const lastChar = fullName[fullName.length - 1];

            if (lastChar === "/") {
              fileType = "directory";
              name = fullName.slice(0, -1);
            } else if (lastChar === "*") {
              fileType = "executable";
              name = fullName.slice(0, -1);
            } else if (lastChar === "@") {
              fileType = "symbolic link";
              name = fullName.slice(0, -1);
            } else {
              let suffix = fullName.split(".");
              fileType = suffix[suffix.length - 1];
            }

            const fileInfo = {
              permissions: parts[0],
              links: parseInt(parts[1]),
              owner: parts[2],
              group: parts[3],
              size: parseInt(parts[4]),
              month: parts[5],
              day: parts[6],
              timeOrYear: parts[7],
              name: name,
              path: filePath,
              formattedDate: formattedDate,
              type: fileType,
              flag: false,
            };
            fileInfoArray.push(fileInfo);
          }
        }
      }

      // 按照文件大小排序
      fileInfoArray.sort((a, b) => b.size - a.size);

      res.send({
        code: 20000,
        msg: "操作成功",
        data: fileInfoArray,
      });
    });
  } catch (error) {
    res.send({
      code: 50000,
      msg: error.message, // 修正为发送错误信息
    });
  }
});

// 添加服务器文件
apiRouter.post("/addServeFile", async (req, res) => {
  let command = "";
  if (req.body.fileType == 1) {
    command = `touch ${req.body.filePath}.txt`; // 新增文件
  } else {
    command = `mkdir -p ${req.body.filePath}`; //新增文件夹
  }
  executeSSHCommand(command, (err, output) => {
    if (err) {
      res.send({
        code: 50000,
        msg: "新增失败" + err,
      });
    }

    res.send({
      code: 20000,
      msg: "新增成功",
    });
  });
});

// 删除服务器文件
apiRouter.post("/delServeFile", async (req, res) => {
  let paths = req.body.path;


  // 判断 fileNames 是否为数组
  if (!Array.isArray(paths)) {
    // 如果不是数组，将其转换为包含单个元素的数组
    paths = [paths];
  }

  // 构建移动文件的命令
  const sourceFiles = paths.join(" ");

  let command = `rm -rf ${sourceFiles}`;


  executeSSHCommand(command, (err, output) => {
    if (err) {
      res.send({
        code: 50000,
        msg: "删除失败" + err,
      });
    }

    res.send({
      code: 20000,
      msg: "删除成功",
      data: output,
    });
  });
});

// 修改服务器文件名称
apiRouter.post("/editServeFile", async (req, res) => {

  let command = `mv ${req.body.oldPath} ${req.body.newPath}`;
  executeSSHCommand(command, (err, output) => {

    if (err) {
      res.send({
        code: 50000,
        msg: "修改失败" + err,
      });
    }
    res.send({
      code: 20000,
      msg: "修改成功",
      data: output,
    });
  });
});

// 向服务器上传文件
apiRouter.post(
  "/uploadServeFile",
  upload.single("file"),
  saveFileData,
  (req, res) => {

    if (!req.file) {
      return res.send({
        code: 40000,
        msg: "未找到上传的文件",
      });
    }

    const localFilePath = req.file.path; // 服务器文件的位置
    const remoteFilePath = `${req.body.serverPath}/${req.file.originalname}`; //上传文件的位置

    const conn = new Client();

    conn
      .on("ready", () => {
        conn.sftp((err, sftp) => {
          if (err) {
            conn.end();
            return res.send({
              code: 50000,
              msg: "打开 SFTP 连接失败: " + err.message,
            });
          }

          const readStream = fs.createReadStream(localFilePath);
          const writeStream = sftp.createWriteStream(remoteFilePath);

          writeStream
            .on("close", () => {
              sftp.end();
              conn.end();
              // 删除本地临时文件
              fs.unlink(localFilePath, (unlinkErr) => {
                if (unlinkErr) {
                  console.error("Error deleting local file:", unlinkErr);
                }
              });
              res.send({
                code: 20000,
                msg: "文件上传成功",
              });
            })
            .on("error", (writeErr) => {
              console.error("Error uploading file:", writeErr);
              sftp.end();
              conn.end();
              res.send({
                code: 50000,
                msg: "文件上传失败: " + writeErr.message,
              });
            });

          readStream.pipe(writeStream);
        });
      })
      .on("error", (sshErr) => {
        res.send({
          code: 50000,
          msg: "SSH 连接失败: " + sshErr.message,
        });
      })
      .connect(config);
  }
);

// 解压服务器压缩文件
apiRouter.post("/decompressionServeFile", async (req, res) => {
  try {
    let command = "";
    // 要解压的文件
    const filePath = req.body.filePath;

    // 要解压的文件目录
    const destination = req.body.destination;

    if (filePath.endsWith(".zip")) {
      command = `unzip ${filePath} -d ${destination}`;
    } else if (filePath.endsWith(".tar")) {
      command = `tar -xvf ${filePath} -C ${destination}`;
    } else if (filePath.endsWith(".tar.gz") || filePath.endsWith(".tgz")) {
      command = `tar -xzvf ${filePath} -C ${destination}`;
    } else if (filePath.endsWith(".tar.bz2")) {
      command = `tar -xjvf ${filePath} -C ${destination}`;
    } else {
      conn.end();
      return;
    }
    executeSSHCommand(command, (err, output) => {
      if (err) {
        res.send({
          code: 50000,
          msg: "解压失败" + err,
        });
      }

      res.send({
        code: 20000,
        msg: "解压成功",
        data: output.split("\n"),
      });
    });
  } catch (error) { }
});

// 移动文件位置
apiRouter.post("/moveServeFile", async (req, res) => {
  try {
    let fileNames = req.body.fileNames; // 源文件位置，可以是单个路径或路径数组
    let destination = req.body.destination; // 目标文件位置

    // 判断 fileNames 是否为数组
    if (!Array.isArray(fileNames)) {
      // 如果不是数组，将其转换为包含单个元素的数组
      fileNames = [fileNames];
    }

    // 构建移动文件的命令
    const sourceFiles = fileNames.join(" ");
    if (req.body.isCopy) {
      command = `cp ${sourceFiles} ${destination}`;
    } else {
      command = `mv ${sourceFiles} ${destination}`;
    }
    // const command = `mv ${sourceFiles} ${destination}`;

    executeSSHCommand(command, (err, output) => {

      if (err) {
        res.send({
          code: 50000,
          msg: "移动失败: " + err.message,
        });
      } else {
        res.send({
          code: 20000,
          msg: "移动成功",
          data: output.split("\n"),
        });
      }
    });
  } catch (error) {
    res.send({
      code: 50000,
      msg: "发生错误: " + error.message,
    });
  }
});

// 获取pm2 管理器的项目列表
apiRouter.post("/getPm2List", async (req, res) => {
  try {
    executeSSHCommand("pm2 list", (err, output) => {
    });
  } catch (error) {
    console.error("操作失败：:", error);
  }
});

module.exports = apiRouter;
